

/* add your code here */
#include <setjmp.h>
#include <stdio.h>
#include <stdlib.h>
#include "mythread.h"

void testing(void);
jmp_buf env;

unsigned long int mangle64(unsigned long int addr)
{
    unsigned long int ret;
    asm volatile("xorq %%fs:0x30,%0\n"

        "rolq $0x11,%0\n"
        : "=r" (ret)
        : "0" (addr));

    return ret;
}

unsigned long int demangle64(unsigned long int addr)
{
    unsigned long int ret;
    asm volatile("rorq $0x11,%0\n"

        "xorq %%fs:0x30,%0\n"
        : "=r" (ret)
        : "0" (addr));

    return ret;
}

/* add your code here */
void testing(){
	printf("Calling longjmp!\n");       

    longjmp(env, 1);
	
    printf("Longjmp returning\n");
}

int main(){
	int character = 40;
	character = character + 2;
	printf("Value of character is: %d\n", character);
	
	if(setjmp(env) != 0){
		/*This is the stack pointer*/
		unsigned long int member6 = demangle64(env->__jmpbuf[6]);
		printf("Stack Pointer/Member 6 of jmp_buf: %lu\n", member6);
		/*This is the program counter */
		unsigned long int member7 = demangle64(env->__jmpbuf[7]);
		printf("Program Counter/Member 7 of jmp_buf: %lu\n", member7);
		
		if(setjmp(env) != 0){
			/*This is the stack pointer*/
			unsigned long int member6 = demangle64(env->__jmpbuf[6]);
			printf("Stack Pointer/Member 6 of jmp_buf: %lu\n", member6);
			/*This is the program counter */
			unsigned long int member7 = demangle64(env->__jmpbuf[7]);
			printf("Program Counter/Member 7 of jmp_buf: %lu\n", member7);
			
			return 0;
		}
		
		testing();
		
		printf("Program terminates normally\n");
	
		return 0;
	}
	
	testing();
	
	printf("Program terminates normally\n");
	
	return 0;
}
